package cn.yuanqiao.archive.danganzhengli.service.impl;


import cn.yuanqiao.activiti.domain.ActivitiPackage;
import cn.yuanqiao.activiti.service.RemoteActivitiService;
import cn.yuanqiao.archive.appManager.domain.*;
import cn.yuanqiao.archive.appManager.mapper.*;
import cn.yuanqiao.archive.appManager.service.ITenantSysConfigService;
import cn.yuanqiao.archive.appManager.service.ITenantSysDictTypeService;
import cn.yuanqiao.archive.danganzhengli.domain.HandOverDa;
import cn.yuanqiao.archive.danganzhengli.domain.HandOverReceive;
import cn.yuanqiao.archive.danganzhengli.mapper.HandOverDaMapper;
import cn.yuanqiao.archive.danganzhengli.mapper.HandOverReceiveMapper;
import cn.yuanqiao.archive.danganzhengli.service.IHandOverReceiveService;
import cn.yuanqiao.archive.danganzhengli.utils.webServiceHttp;
import cn.yuanqiao.archive.wenjianzhengli.mapper.TenantItemFolderMapper;
import cn.yuanqiao.archive.wenjianzhengli.mapper.TenantYqdaFolderMapper;
import cn.yuanqiao.common.core.context.ResponseUtils;
import cn.yuanqiao.common.core.domain.R;
import cn.yuanqiao.common.exception.ServiceException;
import cn.yuanqiao.common.utils.DateUtils;
import cn.yuanqiao.common.utils.StringUtils;
import cn.yuanqiao.common.utils.ZipUtils;
import cn.yuanqiao.common.enums.BusinessBehavior;
import cn.yuanqiao.common.util.BusinessBehaviorUtil;
import cn.yuanqiao.common.utils.SecurityUtils;
import cn.yuanqiao.common.core.domain.model.LoginUser;
import com.alibaba.fastjson.serializer.SerializerFeature;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONArray;
import com.alibaba.fastjson2.JSONObject;
import com.deepoove.poi.XWPFTemplate;
import org.apache.commons.io.FileUtils;
import org.dom4j.Document;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;
import org.dom4j.io.OutputFormat;
import org.dom4j.io.XMLWriter;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ClassPathResource;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @author zjj
 * @date 2023/7/22
 */
@Service
public class HandOverReceiveServiceImpl implements IHandOverReceiveService {
    protected final Logger logger = LoggerFactory.getLogger(this.getClass());

    @Autowired
    private HandOverReceiveMapper handOverReceiveMapper;
    @Autowired
    private ITenantSysConfigService sysConfigService;
    @Autowired
    private TenantMdataListMapper mdataListMapper;
    @Autowired
    private TenantYqdaMapper yqdaMapper;
    @Autowired
    private TenantYqItemMapper itemMapper;
    @Autowired
    private TenantYqFolderMapper folderMapper;
    @Autowired
    private TenantCategoryMapper categoryMapper;
    @Autowired
    private TenantItemFolderMapper itemFolderMapper;
    @Autowired
    private TenantYqdaFolderMapper yqdaFolderMapper;
    @Autowired
    private TenantYqdaDocumentMapper documentMapper;
    @Autowired
    private HandOverDaMapper handOverDaMapper;
    @Autowired
    private TenantCodeListMapper codeListMapper;
    @Autowired
    private RemoteActivitiService activitiService;
    @Autowired
    private ITenantSysDictTypeService sysDictTypeService;


    @Override
    @Transactional
    public int insertHandOverReceive(HandOverReceive handOverReceive) {
        LoginUser user = SecurityUtils.getLoginUser();
        if(handOverReceive.getCreateId() == null){
            handOverReceive.setCreateId(user.getUserId());
        }
        if(handOverReceive.getCreateBy() == null){
            handOverReceive.setCreateBy(user.getUsername());
        }
        if(handOverReceive.getCreateTime() == null){
            handOverReceive.setCreateTime(DateUtils.getDate());
        }
        handOverReceive.setJsState(0);
        handOverReceive.setYjState(0);
        HandOverDa handOverDa = new HandOverDa();
        //添加移交单
        /*if("outLine".equals(handOverReceive.getType())){
            //离线移交不需要审批直接办结
            handOverReceive.setState(2);
            handOverDa.setState(2);
        }else {*/
            //在线移交 移交中
            handOverReceive.setState(1);
            handOverDa.setState(1);
        ////}
        int r = handOverReceiveMapper.insertHandOverReceive(handOverReceive);
        handOverDa.setHandOverId(handOverReceive.getId());
        handOverDa.setCategoryId(handOverReceive.getCategoryId());
        //移交档案添加移交单的关联关系
        handOverDaMapper.updateHandOverId(handOverDa);
        /*if("outLine".equals(handOverReceive.getType())){
            //修改档案状态 已移交
            updateDaStat(handOverReceive.getId(),"7");
        }else {*/
            //修改档案状态 移交中
            //updateDaStat(handOverReceive.getId(),"6");
        ////}

        //发起流程
        ////if("onLine".equals(handOverReceive.getType())){
        HandOverReceive handOverReceives = handOverReceiveMapper.selectHandOverReceiveById(handOverReceive).get(0);
        logger.info(handOverReceives.toString());
        Map<String,Object> variables = new HashMap();
        variables.put("processVariables",handOverReceives.toProcessMap());
        logger.info(variables.toString());
        R<ActivitiPackage> activitiPackageR = activitiService.startProcessWorkFlowArchiveHandOver(variables);
        String activitiId = activitiPackageR.getData().getProcessInstance().getId();
        logger.info("流程ID="+activitiId);
        HandOverReceive update = new HandOverReceive();
        update.setActivitiId(activitiId);
        update.setId(handOverReceive.getId());
        handOverReceiveMapper.updateHandOverReceive(update);
        ////}
        return r;
    }

    public void addBehavior(Long[] ids,String state){
        BusinessBehavior behavior = null;
        if("7".equals(state)){
            behavior = BusinessBehavior.YIJIAO;
        }
        if(null!=behavior){
            List<Long> daIds = Arrays.asList(ids);
            BusinessBehaviorUtil.add(daIds, behavior);
        }
    }

    private void updateDaStat(Long reId,String state){
        HandOverDa select = new HandOverDa();
        select.setHandOverId(reId);
        List<HandOverDa> list = handOverDaMapper.selectHandOverDaList(select);
        for(HandOverDa da:list){
            Integer type = da.getDaType();
            Long id = da.getDaId();
            //1.查询分表表名
            Map<String,Object> data = null;
            if (type == 3){
                data = itemMapper.getItemAllById("SUB_TABLE_NAME",id,new TenantYqItem().getTableName());
            }else if(type == 1){
                data = folderMapper.getYqFolderAllById("SUB_TABLE_NAME",id,new TenantYqFolder().getTableName());
            }else if(type == 0){
                data = yqdaMapper.getYqdaAllById("SUB_TABLE_NAME",id,new TenantYqda().getTableName());
            }
            //2.根据分表查询门类
            TenantCategory category = categoryMapper.selectTenantCategoryByID(da.getCategoryId(),new TenantCategory().getTableName());
            //处理项目层
            Map<String,String> column = new HashMap<>();
            column.put("STATE",state);
            if(category.getType() == 3) {
                //修改项目
                TenantYqItem item = new TenantYqItem();
                item.setColNames(column);
                item.setItemId(id);
                //添加过程信息
                addBehavior(new Long[]{id},state);
                itemMapper.updateItem(item); //主表
                item.setTableName(data.get("SUB_TABLE_NAME").toString());
                itemMapper.updateItemDisperse(item);  //分表

                //修改卷
                Long [] itemId = new Long[]{id};
                Long [] folderIds = folderMapper.getFolderIdsByItemIds(itemId,category.getFolderTableName(),new TenantItemFolder().getTableName());
                //添加过程信息
                addBehavior(folderIds,state);
                for(Long folderId:folderIds){
                    TenantYqFolder yqFolder = new TenantYqFolder();
                    yqFolder.setColNames(column);
                    yqFolder.setFolderId(folderId);
                    folderMapper.updateYqFolder(yqFolder);
                    yqFolder.setTableName(category.getFolderTableName());
                    folderMapper.updateYqFolderDisperse(yqFolder);
                }

                //修改件
                if(folderIds !=null && folderIds.length>0){
                    Long [] daIds = yqdaMapper.getDaIdsByFolderIds(folderIds,category.getFileTableName(),new TenantYqdaFolder().getTableName());
                    //添加过程信息
                    addBehavior(daIds,state);
                    for(Long daId:daIds){
                        TenantYqda yqda = new TenantYqda();
                        yqda.setColNames(column);
                        yqda.setDaId(daId);
                        yqdaMapper.updateYqda(yqda);
                        yqda.setTableName(category.getFileTableName());
                        yqdaMapper.updateYqdaDisperse(yqda);
                    }
                }
            }else if(category.getType() == 1){
                //修改卷
                Long folderId = da.getDaId();
                TenantYqFolder yqFolder = new TenantYqFolder();
                yqFolder.setColNames(column);
                yqFolder.setFolderId(folderId);
                //添加过程信息
                addBehavior(new Long[]{folderId},state);
                folderMapper.updateYqFolder(yqFolder);
                yqFolder.setTableName(category.getFolderTableName());
                folderMapper.updateYqFolderDisperse(yqFolder);

                //修改件
                Long [] folderIds = new Long[]{folderId};
                Long [] daIds = yqdaMapper.getDaIdsByFolderIds(folderIds,category.getFileTableName(),new TenantYqdaFolder().getTableName());
                //添加过程信息
                addBehavior(daIds,state);
                for(Long daId:daIds){
                    TenantYqda yqda = new TenantYqda();
                    yqda.setColNames(column);
                    yqda.setDaId(daId);
                    yqdaMapper.updateYqda(yqda);
                    yqda.setTableName(category.getFileTableName());
                    yqdaMapper.updateYqdaDisperse(yqda);
                }
            } else if(category.getType() == 0){
                //处理组件
                Long daId = da.getDaId();
                TenantYqda yqda = new TenantYqda();
                yqda.setColNames(column);
                yqda.setDaId(daId);
                //添加过程信息
                addBehavior(new Long[]{daId},state);
                yqdaMapper.updateYqda(yqda);
                yqda.setTableName(category.getFileTableName());
                yqdaMapper.updateYqdaDisperse(yqda);
            }
        }
    }

    @Override
    public int getFileCount(Long categoryId) {
        String tenantCode = SecurityUtils.getTenantCode();
        Integer r = handOverReceiveMapper.getFileCount(tenantCode,categoryId);
        return r == null ? 0:r;
    }

    @Override
    public List<HandOverReceive> exportData(Long id) {
        HandOverReceive select = new HandOverReceive();
        select.setId(id);
        List<HandOverReceive> data = handOverReceiveMapper.selectHandOverReceiveById(select);
        data.get(0).setYjTenantCode(SecurityUtils.getTenantCode());
        return data;
    }

    @Override
    public void exportWord(Long id, HttpServletResponse response) throws IOException {
        HandOverReceive select = new HandOverReceive();
        select.setId(id);
        List<HandOverReceive> list = handOverReceiveMapper.selectHandOverReceiveById(select);
        HandOverReceive data = list.get(0);
        Map<String, Object> dataMap = new HashMap<>();
        dataMap.put("name", data.getName());
        dataMap.put("description", data.getDescription());
        dataMap.put("daCount", data.getDaCount());
        dataMap.put("capacity", data.getCapacity());
        if("onLine".equals(data.getType())){
            dataMap.put("onLine", "☑");
            dataMap.put("outLine", "□");
        }else if("outLine".equals(data.getType())){
            dataMap.put("onLine", "□");
            dataMap.put("outLine", "☑");
        }
        dataMap.put("carrier", data.getCarrier());
        dataMap.put("carrierCount", data.getCarrierCount());
        dataMap.put("nd", data.getNd());
        dataMap.put("dh", data.getDh());
        dataMap.put("yjUnit", data.getYjUnit());
        dataMap.put("jsUnit", data.getJsUnit());
        dataMap.put("appearance", data.getAppearance());
        dataMap.put("trueExplain", data.getTrueExplain());
        dataMap.put("integrityExplain", data.getIntegrityExplain());
        dataMap.put("usableExplain",data.getUsableExplain());
        dataMap.put("secureExplain",data.getSecureExplain());
        dataMap.put("writtenBy",data.getWrittenBy());
        dataMap.put("writtenTime",data.getWrittenTime());
        dataMap.put("auditorBy",data.getAuditorBy());
        dataMap.put("auditorTime",data.getAuditorTime());
        dataMap.put("unitBy",data.getUnitBy());
        dataMap.put("unitTime",data.getUnitTime());

        String uplodPath = sysConfigService.selectConfigByKey("YQ_YIJIAO");
        if(StringUtils.isEmpty(uplodPath)){
            throw new ServiceException("系统参数错误YQ_YIJIAO未找到配置！");
        }
        File filePath = new File(uplodPath+"model"+File.separator);
        if(!filePath.exists()){
            filePath.mkdirs();
        }
        File outputFile = new File(uplodPath+"model"+File.separator+"yijiao.docx");
        if(!outputFile.exists()){
            outputFile.createNewFile();
            ClassPathResource classPathResource = new ClassPathResource("yijiaoModel/yijiao.docx");
            InputStream inputStream = null;
            OutputStream outputStream1 = null;
            try {
                inputStream = classPathResource.getInputStream();
                // 创建输出文件的输出流
                outputStream1 = new FileOutputStream(outputFile);
                // 创建一个缓冲区，用于高效的数据传输
                byte[] buffer = new byte[1024];
                int bytesRead;
                // 从输入流中读取数据，并写入到输出流中
                while ((bytesRead = inputStream.read(buffer)) != -1) {
                    outputStream1.write(buffer, 0, bytesRead);
                }
            }catch (Exception e){
                throw e;
            }finally {
                // 刷新并关闭流
                if(outputStream1 !=null){
                    outputStream1.flush();
                }
                if(inputStream !=null){
                    inputStream.close();
                }
                if(outputStream1 !=null){
                    outputStream1.close();
                }
            }
        }

        //文件输出地址，指定到文件
        String outPath = uplodPath+"doc"+File.separator+id+".docx";
        File dest = new File(outPath);
        if (!dest.getParentFile().exists())
        {
            dest.getParentFile().mkdirs();// 新建文件夹
        }
        XWPFTemplate render = XWPFTemplate.compile(outputFile).render(dataMap);
        render.writeToFile(outPath);

        File file = new File(outPath);
        FileInputStream fileInputStream = null;
        InputStream fis = null;
        byte[] buffer = null;
        try {
            fileInputStream = new FileInputStream(file);
            fis = new BufferedInputStream(fileInputStream);
            buffer = new byte[fis.available()];
            fis.read(buffer);
        }catch (Exception e){

        }finally {
            if(fis!=null){
                fis.close();
            }
            if(fileInputStream !=null){
                fileInputStream.close();
            }
        }


        // 清空response
        response.reset();
        ResponseUtils.defaultResponse(response);
        // 设置response的Header
        response.setCharacterEncoding("UTF-8");
        //Content-Disposition的作用：告知浏览器以何种方式显示响应返回的文件，用浏览器打开还是以附件的形式下载到本地保存
        //attachment表示以附件方式下载   inline表示在线打开   "Content-Disposition: inline; filename=文件名.mp3"
        // filename表示文件的默认名称，因为网络传输只支持URL编码的相关支付，因此需要将文件名URL编码后进行传输,前端收到后需要反编码才能获取到真正的名称
        response.addHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode("电子档案移交与接收登记表.docx", "UTF-8"));
        // 告知浏览器文件的大小
        response.addHeader("Content-Length", "" + file.length());
        OutputStream outputStream = new BufferedOutputStream(response.getOutputStream());
        response.setContentType("application/octet-stream");
        outputStream.write(buffer);
        outputStream.flush();

    }

    @Override
    public HandOverReceive selectHandOverReceiveById(HandOverReceive handOverReceive) {
        List<HandOverReceive> list = handOverReceiveMapper.selectHandOverReceiveById(handOverReceive);
        HandOverReceive data = list.size()!=0?list.get(0):new HandOverReceive();
        return data;
    }

    @Override
    public void yijiaopack(Long id, HttpServletResponse response) throws IOException{
        HandOverReceive selectRE = new HandOverReceive();
        selectRE.setId(id);
        List<HandOverReceive> receive = handOverReceiveMapper.selectHandOverReceiveById(selectRE);
        if(receive.size() == 0 || receive.get(0).getState()!=2){
            throw new ServiceException("当前移交单未流转完成，不能下载！");
        }
        HandOverDa select = new HandOverDa();
        select.setHandOverId(id);
        select.setState(2);
        List<HandOverDa> list = handOverDaMapper.selectHandOverDaList(select);
        String yijiaoPack = sysConfigService.selectConfigByKey("YQ_YIJIAO");
        if(StringUtils.isEmpty(yijiaoPack)){
            throw new ServiceException("系统参数错误YQ_YIJIAO未找到配置！");
        }
        //验证压缩包是否存在，存在就直接下载
        File packZip = new File(yijiaoPack + id + ".zip");
        if(!packZip.exists()){
            String yijiao = yijiaoPack + id + File.separator;
            File file = new File(yijiao);
            if(file.exists()){
                //删除目录重新生成
                FileUtils.deleteQuietly(file);
            }
            //生成移交文件
            for(HandOverDa overDa:list){
                packXml(yijiao,overDa.getDaId(),overDa.getDaType());
            }
            //打压缩包
            ZipUtils.zip(yijiao,yijiaoPack+id);
            //生成后删除临时文件
            FileUtils.deleteQuietly(file);
        }
        //标记状态为已移交
        HandOverReceive receiveUpdate = new HandOverReceive();
        receiveUpdate.setId(id);
        receiveUpdate.setYjState(1);
        handOverReceiveMapper.updateHandOverReceive(receiveUpdate);
        //下载文件。
        download(packZip,response);
    }

    private void download(File file,HttpServletResponse response) throws IOException{
        // 获取文件名
        String filename = file.getName();
        // 将文件写入输入流
        FileInputStream fileInputStream = new FileInputStream(file);
        InputStream fis = new BufferedInputStream(fileInputStream);
        byte[] buffer = new byte[fis.available()];
        fis.read(buffer);
        fis.close();
        // 清空response
        response.reset();
        ResponseUtils.defaultResponse(response);
        // 设置response的Header
        response.setCharacterEncoding("UTF-8");
        //Content-Disposition的作用：告知浏览器以何种方式显示响应返回的文件，用浏览器打开还是以附件的形式下载到本地保存
        //attachment表示以附件方式下载   inline表示在线打开   "Content-Disposition: inline; filename=文件名.mp3"
        // filename表示文件的默认名称，因为网络传输只支持URL编码的相关支付，因此需要将文件名URL编码后进行传输,前端收到后需要反编码才能获取到真正的名称
        response.addHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(filename, "UTF-8"));
        // 告知浏览器文件的大小
        response.addHeader("Content-Length", "" + file.length());
        OutputStream outputStream = new BufferedOutputStream(response.getOutputStream());
        response.setContentType("application/octet-stream");
        outputStream.write(buffer);
        outputStream.flush();
    }

    @Override
    public List<HandOverReceive> selectHandOverReceive(HandOverReceive receive){
        return handOverReceiveMapper.selectHandOverReceive(receive);
    }

    @Override
    public String getFileSize(Long categoryId) {
        String tenantCode = SecurityUtils.getTenantCode();
        List<Map<String,Object>> list = handOverDaMapper.selectHandOverDaNoReId(tenantCode);
        Long fileSize = 0L;
        for(Map<String,Object> data:list){
            //查询档案所在门类
            TenantCategory category = categoryMapper.selectTenantCategoryByID(categoryId,new TenantCategory().getTableName());
            //查询电子文件表
            List<Map<String,Object>> efileMap = documentMapper.getDocumentBydaId("DOC_FILE_SIZE",Long.valueOf(data.get("DA_ID").toString()),category.getEfileTableName(),"");
            for(Map<String,Object> efile:efileMap){
                if(efile.get("DOC_FILE_SIZE")!=null && !"".equals(efile.get("DOC_FILE_SIZE").toString())){
                    fileSize+=Long.valueOf(efile.get("DOC_FILE_SIZE").toString());
                }
            }
        }
        return formatFileSize(fileSize);
    }


    @Override
    public int jsState(Long id,String tenantCode) {
        HandOverDa handOverDa = new HandOverDa();
        handOverDa.setState(66);  //已接收
        handOverDa.setHandOverId(id);
        handOverDa.setTableName(tenantCode+"_HAND_OVER_DA");
        handOverDaMapper.updateHandOverByReId(handOverDa);

        HandOverReceive receive = new HandOverReceive();
        receive.setId(id);
        receive.setJsState(1);   //已接收
        receive.setTableName(tenantCode+"_HAND_OVER_RECEIVE");
        return handOverReceiveMapper.updateHandOverReceive(receive);
    }

    @Override
    @Transactional
    public int yijiaoBanjie(Long id) {
        HandOverDa handOverDa = new HandOverDa();
        handOverDa.setState(2);
        handOverDa.setHandOverId(id);
        handOverDaMapper.updateHandOverByReId(handOverDa);

        HandOverReceive handOverReceive = new HandOverReceive();
        handOverReceive.setId(id);
        handOverReceive.setState(2);

        //updateDaStat(id,"7");
        return handOverReceiveMapper.updateHandOverReceive(handOverReceive);
    }

    /**
     * 文件大小智能转换
     * 会将文件大小转换为最大满足单位
     * @param size（文件大小，单位为B）
     * @return 文件大小
     */
    public static String formatFileSize(Long size) {
        String sizeName = null;
        if(1024*1024 > size && size >= 1024 ) {
            sizeName = String.format("%.2f",size.doubleValue()/1024) + "KB";
        }else if(1024*1024*1024 > size && size >= 1024*1024 ) {
            sizeName = String.format("%.2f",size.doubleValue()/(1024*1024)) + "MB";
        }else if(size >= 1024*1024*1024 ) {
            sizeName = String.format("%.2f",size.doubleValue()/(1024*1024*1024)) + "GB";
        }else {
            sizeName = size.toString() + "B";
        }
        //sizeName = String.format("%.2f",size.doubleValue()/(1024*1024*1024));  //转换成GB
        return sizeName;
    }
    @Override
    public void packXml(String path,Long id,Integer type){
        try {
            //1.查询分表表名
            Map<String,Object> data = null;
            if (type == 3){
                data = itemMapper.getItemAllById("SUB_TABLE_NAME",id,new TenantYqItem().getTableName());
            }else if(type == 1){
                data = folderMapper.getYqFolderAllById("SUB_TABLE_NAME",id,new TenantYqFolder().getTableName());
            }else if(type == 0){
                data = yqdaMapper.getYqdaAllById("SUB_TABLE_NAME",id,new TenantYqda().getTableName());
            }
            //2.根据分表查询门类
            TenantCategory category = categoryMapper.selectTenantCategoryByTableName(String.valueOf(data.get("SUB_TABLE_NAME")),new TenantCategory().getTableName());
            //3.查询元数据方案
            TenantMdataList selectMList = new TenantMdataList();
            selectMList.setIsMetadata(1); //是元数据项的
            selectMList.setGroupId(category.getGroupId());
            List<TenantMdataList> mdataLists = mdataListMapper.selectTenantMdataListList(selectMList);

            if(category.getType() == 3 || category.getType() == 1){
                //获取项目下的卷
                List<String> folderIds = new ArrayList<>();
                if(category.getType() == 3 ){
                    folderIds = itemFolderMapper.selectFolderIdByItemId(String.valueOf(id),new TenantItemFolder().getTableName());
                }else {
                    folderIds.add(String.valueOf(id));
                }
                for(String folderId:folderIds){
                    //构建xml
                    Document document = DocumentHelper.createDocument();
                    Element dast = createTitleXml(document,category.getType());

                    //查询卷信息
                    Map<String,Object> juanMap = folderMapper.getYqFolderById(getColumn(mdataLists,1),Long.valueOf(folderId),category.getFolderTableName());
                    if(juanMap!= null && "0".equals(String.valueOf(juanMap.get("IS_DEL")))){
                        if(juanMap.get("DH") == null || "".equals(juanMap.get("DH").toString())){
                            throw new ServiceException("卷层档号没有值,打包失败！");
                        }
                        //档号值
                        dast.addElement("电子档案号").addText(String.valueOf(juanMap.get("DH")));

                        //创建档号节点
                        String jianDH = createDhXml(dast,juanMap.get("RQ"),category,"v",folderId);

                        Element daXml = dast.addElement("内容描述");

                        //创建卷
                        for(TenantMdataList mdata:mdataLists){
                            if(mdata.getType() == 1){
                                Element e = daXml.addElement(mdata.getFieldCaption());
                                if(mdata.getShowType() == 5){
                                    e.addText(getDictVal(mdata.getFieldName(),juanMap.get(mdata.getFieldName())));
                                }else {
                                    e.addText(getNull(juanMap.get(mdata.getFieldName())));
                                }

                            }
                        }
                        //创建项目层
                        if(category.getType() == 3){
                            Map<String,Object> xmMap = folderMapper.getYqFolderById(getColumn(mdataLists,3),id,category.getItemTableName());
                            Element xm = daXml.addElement("项目层");
                            for(TenantMdataList mdata:mdataLists){
                                if(mdata.getType() == 3){
                                    Element e = xm.addElement(mdata.getFieldCaption());
                                    if(mdata.getShowType() == 5){
                                        e.addText(getDictVal(mdata.getFieldName(),xmMap.get(mdata.getFieldName())));
                                    }else {
                                        e.addText(getNull(xmMap.get(mdata.getFieldName())));
                                    }

                                }
                            }
                        }
                        //创建件层
                        List<String> daIds = yqdaFolderMapper.selectFileIdByFolderId(folderId,new TenantYqdaFolder().getTableName());
                        Element jianList = daXml.addElement("件层集");
                        TenantMdataList mdataList = new TenantMdataList();
                        mdataList.setGroupId(category.getGroupId());
                        mdataList.setType(0);
                        mdataList.setFieldName(jianDH);
                        List<TenantMdataList> lastDhJian = mdataListMapper.selectTenantMdataListList(mdataList);
                        mdataLists.addAll(lastDhJian);
                        List<TenantMdataList> mdataListsJian = mdataLists.stream().distinct().collect(Collectors.toList());
                        for(String daId:daIds) {
                            Map<String,Object> jianMap = yqdaMapper.getYqdaById(getColumn(mdataListsJian,0),Long.valueOf(daId),category.getFileTableName());
                            if("0".equals(String.valueOf(jianMap.get("IS_DEL")))) {
                                Element jian = jianList.addElement("件层");
                                for(TenantMdataList mdata:mdataListsJian){
                                    if(mdata.getType() == 0){
                                        Element e = jian.addElement(mdata.getFieldCaption());
                                        if(mdata.getShowType() == 5){
                                            e.addText(getDictVal(mdata.getFieldName(),jianMap.get(mdata.getFieldName())));
                                        }else {
                                            e.addText(getNull(jianMap.get(mdata.getFieldName())));
                                        }
                                    }
                                }
                                //创建电子文件节点
                                createDocXml(mdataLists,daId,category,jian,juanMap.get("DH").toString(),jianMap.get("DH").toString(),path);
                            }
                        }
                    }

                    //固定节点
                    dast.addElement("形式特征").addElement("文件组合类型").addText("单件");
                    dast.addElement("存储位置").addElement("脱机载体编号").addText("");
                    dast.addElement("权限管理").addText("");
                    //写入文件
                    writer(path+File.separator+juanMap.get("DH")+File.separator,document);
                }
            }else if(category.getType() == 0){
                //构建xml
                Document document = DocumentHelper.createDocument();
                Element dast = createTitleXml(document,category.getType());
                Map<String,Object> jianMap = yqdaMapper.getYqdaById(getColumn(mdataLists,0),id,category.getFileTableName());
                if(jianMap!= null && "0".equals(String.valueOf(jianMap.get("IS_DEL")))) {
                    if(jianMap.get("DH") == null || "".equals(jianMap.get("DH").toString())){
                        throw new ServiceException("件层档号没有值,打包失败！");
                    }
                    dast.addElement("电子档案号").addText(String.valueOf(jianMap.get("DH")));
                    //创建档号节点
                    createDhXml(dast,jianMap.get("RQ"),category,"f",String.valueOf(id));

                    Element daXml = dast.addElement("内容描述");
                    for(TenantMdataList mdata:mdataLists){
                        if(mdata.getType() == 0){
                            Element e = daXml.addElement(mdata.getFieldCaption());
                            if(mdata.getShowType() == 5){
                                e.addText(getDictVal(mdata.getFieldName(),jianMap.get(mdata.getFieldName())));
                            }else {
                                e.addText(getNull(jianMap.get(mdata.getFieldName())));
                            }

                        }
                    }
                    //创建电子文件节点
                    createDocXml(mdataLists,String.valueOf(id),category,daXml,null,jianMap.get("DH").toString(),path);
                }


                //固定节点
                dast.addElement("形式特征").addElement("文件组合类型").addText("单件");
                dast.addElement("存储位置").addElement("脱机载体编号").addText("");
                dast.addElement("权限管理").addText("");
                //写入文件
                writer(path+File.separator+jianMap.get("DH")+File.separator,document);
            }
        }catch (Exception e){
            logger.error(e.getMessage(),e);
            throw new ServiceException("打包失败:"+e.getMessage());
        }

    }

    /**
     * 字典项
     * @param fieldName
     * @param dict
     * @return
     */
    private String getDictVal(String fieldName,Object dict){

        String DictVal = "";
        List<TenantSysDictData> list = sysDictTypeService.selectDictDataByType(fieldName);
        if(list!=null && list.size()>0){
            if(dict!=null) {
                for (TenantSysDictData dictData : list) {
                    if (String.valueOf(dict).equals(dictData.getDictValue())) {
                        DictVal = dictData.getDictLabel();
                        break;
                    }
                }
            }
        }else {
            DictVal = getNull(dict);
        }
        return DictVal;
    }

    @Override
    @Transactional
    public int killHOV(Long id) {
        //流程审批不同意 修改移交单状态
        HandOverReceive receive = new HandOverReceive();
        receive.setState(99);
        receive.setId(id);
        int r = handOverReceiveMapper.updateHandOverReceive(receive);
        //修改移交档案中移交状态
        HandOverDa overDa = new HandOverDa();
        overDa.setState(99);
        overDa.setHandOverId(id);
        handOverDaMapper.updateHandOverByReId(overDa);
        //状态再改回档案整理
        //updateDaStat(id,"5");
        return r;
    }

    @Override
    public String onlinpush(Long[] ids) {
        //state 0创建 1流程中 2流程结束  5退回 6部分接收?
        //yjstate 1成功推送
        String returnmsg="";
        //先更新包信息
        String yijiaoPack = sysConfigService.selectConfigByKey("YQ_YIJIAO");
        JSONArray array=new JSONArray(ids.length);
        String errormsg="";
        for(Long id:ids){
            HandOverReceive receive=new HandOverReceive();
            receive.setId(id);
            receive.setYjState(0); //未移交
            receive.setState(2);  //已办结
            List<HandOverReceive> handOverReceivesList = handOverReceiveMapper.selectHandOverReceiveById(receive);
            HandOverReceive handOverReceives = null;
            if(handOverReceivesList.size()>0){
                handOverReceives = handOverReceivesList.get(0);
            }else {
                //已推送的数据不再推送
                continue;
            }

            //验证压缩包是否存在，存在就直接下载
            Long categoryId=0L;
            File packZip = new File(yijiaoPack + id + ".zip");
            HandOverDa select = new HandOverDa();
            select.setHandOverId(id);
            select.setState(2);
            List<HandOverDa> list = handOverDaMapper.selectHandOverDaList(select);
            if(list.size()==0){
                errormsg+="移交单id=="+id+"的档案数据为空";
                continue;
            }else{
                Map<String,Object> data = null;
                if (list.get(0).getDaType() == 3){
                    data = itemMapper.getItemAllById("SUB_TABLE_NAME",list.get(0).getDaId(),new TenantYqItem().getTableName());
                }else if(list.get(0).getDaType() == 1){
                    data = folderMapper.getYqFolderAllById("SUB_TABLE_NAME",list.get(0).getDaId(),new TenantYqFolder().getTableName());
                }else if(list.get(0).getDaType() == 0){
                    data = yqdaMapper.getYqdaAllById("SUB_TABLE_NAME",list.get(0).getDaId(),new TenantYqda().getTableName());
                }
                //2.根据分表查询门类
                TenantCategory category = categoryMapper.selectTenantCategoryByTableName(String.valueOf(data.get("SUB_TABLE_NAME")),new TenantCategory().getTableName());
                categoryId=category.getId();
            }

            if(!packZip.exists()){
                String yijiao = yijiaoPack + id + File.separator;
                File file = new File(yijiao);
                if(file.exists()){
                    //删除目录重新生成
                    FileUtils.deleteQuietly(file);
                }

                //生成移交文件
                for(HandOverDa overDa:list){
                    packXml(yijiao,overDa.getDaId(),overDa.getDaType());
                }
                //打压缩包
                ZipUtils.zip(yijiao,yijiaoPack+id);
                //生成后删除临时文件
                FileUtils.deleteQuietly(file);
            }
            //标记状态为已移交
            HandOverReceive receiveUpdate = new HandOverReceive();
            receiveUpdate.setId(id);
            receiveUpdate.setPacketPath(yijiaoPack+id+".zip");
            handOverReceiveMapper.updateHandOverReceive(receiveUpdate);

            JSONObject json=new JSONObject();
            json.put("name",handOverReceives.getName()); //交接工作名称
            json.put("description",handOverReceives.getDescription());//内容描述
            json.put("daCount",handOverReceives.getDaCount());//移交电子档案数量
            json.put("capacity",handOverReceives.getCapacity());//移交数据容量
            json.put("type",handOverReceives.getType());//移交类型
            json.put("carrier",handOverReceives.getCarrier());//移交载体类型
            json.put("carrierCount",handOverReceives.getCarrierCount());//移交载体数量
            json.put("nd",handOverReceives.getNd());//移交电子档案起止年度
            json.put("dh",handOverReceives.getDh());//移交电子档案起止档号
            json.put("yjUnit",handOverReceives.getYjUnit());//移交单位名称
            json.put("jsUnit",handOverReceives.getJsUnit());//接收单位
            json.put("appearance",handOverReceives.getAppearance());//载体外观检测
            json.put("trueExplain",handOverReceives.getTrueExplain());//真实性检测
            json.put("integrityExplain",handOverReceives.getIntegrityExplain());//完整性检测
            json.put("usableExplain",handOverReceives.getUsableExplain());//可用性检测
            json.put("secureExplain",handOverReceives.getSecureExplain());//安全性检测
            json.put("createBy",handOverReceives.getCreateBy());//创建者
            json.put("createTime",handOverReceives.getCreateTime());//移交时间
            json.put("auditorBy",handOverReceives.getAuditorBy());//移交单位审核人
            json.put("unitBy",handOverReceives.getUnitBy());//单位
            json.put("unitTime",handOverReceives.getUnitTime());//单位
            json.put("auditorTime",handOverReceives.getAuditorTime());//移交单位审核日期
            json.put("illustrate",handOverReceives.getIllustrate());//说明、意见
            json.put("writtenBy",handOverReceives.getWrittenBy());//移交单位填表人
            json.put("writtenTime",handOverReceives.getWrittenTime());//移交单位填表日期
            json.put("categoryId",categoryId);//门类id
            json.put("packetPath",yijiaoPack+id+".zip");
            json.put("tenantCode",SecurityUtils.getTenantCode());
            json.put("biaoShi",handOverReceives.getId());
            array.add(com.alibaba.fastjson.JSON.toJSONString(json, SerializerFeature.WriteMapNullValue));
        }
        logger.debug("jsonarr====="+array.toString());
        logger.error(errormsg);
        String url = sysConfigService.selectConfigByKey("sendOnlineUrl");
        if(StringUtils.isEmpty(url)){
            throw new ServiceException("请配置系统参数“sendOnlineUrl”，在线发送地址！");
        }
        //推送
        //String url="http://"+instance.getIp()+":"+instance.getPort()+"/webservice/archiveWebService?wsdl";
        //构造xml参数
        StringBuffer sb = new StringBuffer();
        sb.append("<?xml version=\"1.0\" encoding=\"UTF-8\"?><soapenv:Envelope xmlns:soapenv=\"http://schemas.xmlsoap.org/soap/envelope/\" xmlns:xsd=\"http://www.w3.org/2001/XMLSchema\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\"><soapenv:Body>" +
                "<ns1:saveOnlineArchive soapenv:encodingStyle=\"http://schemas.xmlsoap.org/soap/encoding/\" " +
                "xmlns:ns1=\"http://service.webservice.archive.yuanqiao.cn\">" +
                "<paketInfo xsi:type=\"xsd:string\">"+array.toString()+"</paketInfo>" +
                "</ns1:saveOnlineArchive></soapenv:Body></soapenv:Envelope>");
        try {
            returnmsg = webServiceHttp.sendWebService(url, "archiveWebService", "saveOnlineArchive", sb);
            System.out.println(returnmsg);
        } catch (Exception e) {
            e.printStackTrace();
        }
        if(null!=returnmsg&&!"".equals(returnmsg)){
            JSONObject jsonObject = JSON.parseObject(returnmsg);
            JSONArray success=jsonObject.getJSONArray("success");
            JSONArray fail=jsonObject.getJSONArray("fail");
            logger.info(success.toString()+"成功!"+fail.toString()+"失败!");
            for (int i = 0; i < success.size(); i++) {
                HandOverReceive receiveUpdate = new HandOverReceive();
                receiveUpdate.setId(Long.parseLong(String.valueOf(success.get(i))));
                receiveUpdate.setYjState(1);//已成功推送
                handOverReceiveMapper.updateHandOverReceive(receiveUpdate);
            }
            return "成功"+success.size()+"条,失败"+fail.size()+"条";
        }
        return null;
    }

    @Override
    public int insertNewHandOverReceive(HandOverReceive handOverReceive) {
        LoginUser user = SecurityUtils.getLoginUser();
        if(handOverReceive.getCreateId() == null){
            handOverReceive.setCreateId(user.getUserId());
        }
        if(handOverReceive.getCreateBy() == null){
            handOverReceive.setCreateBy(user.getUsername());
        }
        if(handOverReceive.getCreateTime() == null){
            handOverReceive.setCreateTime(DateUtils.getDate());
        }
        handOverReceive.setJsState(0);
        handOverReceive.setYjState(0);
        HandOverDa handOverDa = new HandOverDa();
        //添加移交单
        /*if("outLine".equals(handOverReceive.getType())){
            //离线移交不需要审批直接办结
            handOverReceive.setState(2);
            handOverDa.setState(2);
        }else {*/
        //在线移交 移交中
        handOverReceive.setState(1);
        handOverDa.setState(1);
        ////}
        int r = handOverReceiveMapper.insertHandOverReceive(handOverReceive);
        handOverDa.setHandOverId(handOverReceive.getId());
        handOverDa.setCategoryId(handOverReceive.getCategoryId());
        //移交档案添加移交单的关联关系
        handOverDaMapper.updateHandOverId(handOverDa);
        /*if("outLine".equals(handOverReceive.getType())){
            //修改档案状态 已移交
            updateDaStat(handOverReceive.getId(),"7");
        }else {*/
        //修改档案状态 移交中
        //updateDaStat(handOverReceive.getId(),"6");
        ////}

        //发起流程
        ////if("onLine".equals(handOverReceive.getType())){
            /*HandOverReceive handOverReceives = handOverReceiveMapper.selectHandOverReceiveById(handOverReceive).get(0);
            logger.info(handOverReceives.toString());
            Map<String,Object> variables = new HashMap();
            variables.put("processVariables",handOverReceives.toProcessMap());
            logger.info(variables.toString());
            R<ActivitiPackage> activitiPackageR = activitiService.startProcessWorkFlowArchiveHandOver(variables);
            String activitiId = activitiPackageR.getData().getProcessInstance().getId();
            logger.info("流程ID="+activitiId);
            HandOverReceive update = new HandOverReceive();
            update.setActivitiId(activitiId);
            update.setId(handOverReceive.getId());
            handOverReceiveMapper.updateHandOverReceive(update);*/
        ////}
        //不发起流程直接办结
        yijiaoBanjie(handOverReceive.getId());
        return r;
    }

    /**
     * 创建部分固定节点
     * @param document
     * @param type
     * @return
     */
    private Element createTitleXml( Document document,Integer type){
        Element root = document.addElement("电子档案封装包");
        root.addElement("封装包格式描述").addText("本EEP根据中华人民共和国档案行业标准DA/T 48-2009《基于XML的电子文件封装规范》生成");
        root.addElement("版本").addText("2009");
        Element dx = root.addElement("被签名对象");
        dx.addElement("封装包类型").addText("原始型");
        dx.addElement("封装包类型描述").addText("本封装包包含电子档案数据及其元数据，原始封装，未经修改");
        dx.addElement("封装包创建时间").addText(DateUtils.getTime());
        String depeName = SecurityUtils.getLoginUser().getUser().getDept().getParentName();
        dx.addElement("封装包创建单位").addText(StringUtils.isNotEmpty(depeName) ? depeName:"");
        Element info = dx.addElement("封装内容");
        Element dast = info.addElement("档案实体块");
        dast.addElement("聚合层次").addText(type == 0 ? "文件":"组卷");
        dast.addElement("来源").addElement("立档单位名称").addText("");
        return dast;
    }

    /**
     * 创建档号节点
     * @param dast
     * @param RQ
     * @param category
     * @param type
     * @param daId
     */
    private String createDhXml(Element dast, Object RQ, TenantCategory category, String type, String daId){
        String jianDh = "";
        //档号组成
        List<Map<String,String>> rule = null;
        if(RQ!=null && StringUtils.isNotEmpty(String.valueOf(RQ))){
            //根据日期获取档号规则
            rule = codeListMapper.getCodeListByCategoryId(category.getId(),new TenantCodeList().getTableName(),new TenantCodeRule().getTableName(),
                    Integer.valueOf(String.valueOf(RQ)),"著录项值",type);
            if(rule != null && rule.size()>0 && "v".equals(type)){
                //获取档号卷内件的存贮字段
                List<Map<String,String>> jianrule = codeListMapper.getCodeListByCategoryId(category.getId(),new TenantCodeList().getTableName(),new TenantCodeRule().getTableName(),
                        Integer.valueOf(String.valueOf(RQ)),"著录项值","f");
                if(jianrule != null && jianrule.size()>0){
                    jianDh = jianrule.get(0).get("NODE_VALUE");
                }
            }
        }
        if(rule == null || rule.size()==0){
            //使用默认档号规则
            rule = codeListMapper.getCodeListByCategoryId(category.getId(),new TenantCodeList().getTableName(),new TenantCodeRule().getTableName(),null,"著录项值",type);
            if(rule != null && rule.size()>0 && "v".equals(type)){
                //获取档号卷内件的存贮字段
                List<Map<String,String>> jianrule =new ArrayList<>();
                if(StringUtils.isEmpty(String.valueOf(RQ))){
                    jianrule = codeListMapper.getCodeListByCategoryId(category.getId(),new TenantCodeList().getTableName(),new TenantCodeRule().getTableName(),
                            Integer.valueOf(String.valueOf(RQ)),"著录项值","f");
                }else{
                    jianrule = codeListMapper.getCodeListByCategoryId(category.getId(),new TenantCodeList().getTableName(),new TenantCodeRule().getTableName(),
                            null,"著录项值","f");
                }
                if(jianrule != null && jianrule.size() > 0){
                    jianDh = jianrule.get(0).get("NODE_VALUE");
                }
            }
        }
        if(rule != null || rule.size()!=0){
            Element dhXml = dast.addElement("档号");
            StringBuilder selectSql = new StringBuilder();
            List<String> selectCol = new ArrayList<>();
            for(int i = 0;i<rule.size();i++){
                selectSql.append(rule.get(i).get("NODE_VALUE")+",");
                selectCol.add(rule.get(i).get("NODE_VALUE"));
            }
            if(selectSql.length()>0){
                selectSql.append("IS_DEL");
                TenantMdataList select = new TenantMdataList();
                select.setGroupId(category.getGroupId());
                select.setType("f".equals(type) ? 0:1);
                //查询组成档号字段的元数据明细
                List<TenantMdataList> mdataLists = mdataListMapper.selectByFieldName(selectCol,select);
                if("v".equals(type)){
                    //查询组成档号字段的值
                    Map<String,Object> juanDhMap = folderMapper.getYqFolderById(selectSql.toString(),Long.valueOf(daId),category.getFolderTableName());
                    for(Map<String,String> dhCol:rule){
                        for(TenantMdataList mdata:mdataLists){
                            if(mdata.getType() == 1 && dhCol.get("NODE_VALUE").equals(mdata.getFieldName())){
                                //档号节点内容
                                dhXml.addElement(mdata.getFieldCaption()).addText(getNull(juanDhMap.get(dhCol.get("NODE_VALUE"))));
                            }
                        }
                    }
                    //件档号组成字段
                    if(StringUtils.isNotEmpty(jianDh)){
                        select.setType(0);
                        selectCol = new ArrayList<>();
                        selectCol.add(jianDh);
                        List<TenantMdataList> jianMdataLists = mdataListMapper.selectByFieldName(selectCol,select);
                        if(jianMdataLists!=null && jianMdataLists.size()>0){
                            dhXml.addElement("件档号组成字段").addText(jianMdataLists.get(0).getFieldCaption());
                        }else {
                            dhXml.addElement("件档号组成字段").addText("没有相关配置");
                        }
                    }else {
                        dhXml.addElement("件档号组成字段").addText("没有相关配置");
                    }
                }else if("f".equals(type)){
                    Map<String,Object> jianDhMap = yqdaMapper.getYqdaById(selectSql.toString(),Long.valueOf(daId),category.getFileTableName());
                    for(Map<String,String> dhCol:rule){
                        for(TenantMdataList mdata:mdataLists){
                            if(mdata.getType() == 0 && dhCol.get("NODE_VALUE").equals(mdata.getFieldName())){
                                //档号节点内容
                                dhXml.addElement(mdata.getFieldCaption()).addText(getNull(jianDhMap.get(dhCol.get("NODE_VALUE"))));
                            }
                        }
                    }
                }

            }
        }else {
            throw new ServiceException("没有配置档号规则!");
        }
        return jianDh;
    }

    /**
     * 创建电子文件节点
     * @param mdataLists
     * @param daId
     * @param category
     * @param jian
     * @param juanDh
     * @param jianDh
     * @param path
     * @throws IOException
     */
    private void createDocXml(List<TenantMdataList> mdataLists, String daId, TenantCategory category, Element jian, String juanDh, String jianDh, String path) throws IOException{
        //电子文件层
        List<Map<String, Object>> docList = documentMapper.getDocumentBydaId(getColumn(mdataLists,2),Long.valueOf(daId),category.getEfileTableName(),"");
        Element docXmlList = jian.addElement("文件数据集");
        for(Map<String, Object> docMap:docList){
            if("0".equals(String.valueOf(docMap.get("IS_DEL")))){
                Element wd = docXmlList.addElement("文件数据").addElement("文档");
                wd.addElement("文档标识符").addText("");
                wd.addElement("文档主从声明").addText(getNull(docMap.get("TYPE")));
                Element bm = wd.addElement("文档数据").addElement("编码");
                Element dzsx = bm.addElement("电子属性");

                //复制档案到对应路径下
                String docPath = sysConfigService.selectConfigByKey("YQ_MNT");
                File file = new File(docPath+docMap.get("PATH"));
                if(file.exists()){
                    String yijiaoPack = path+(StringUtils.isNotEmpty(juanDh) ? (juanDh+File.separator):"")+jianDh+File.separator;
                    File toFile = new File(yijiaoPack);
                    if(!toFile.exists()){
                        toFile.mkdirs();
                    }
                    FileUtils.copyFile(file,new File(yijiaoPack+docMap.get("REAL_DOC_NAME")));
                }
                for(TenantMdataList docMdata:mdataLists){
                    if(docMdata.getType() == 2){
                        Element docXml = dzsx.addElement(docMdata.getFieldCaption());
                        if(docMdata.getShowType() == 5){
                            docXml.addText(getDictVal(docMdata.getFieldName(),docMap.get(docMdata.getFieldName())));
                        }else {
                            docXml.addText(getNull(docMap.get(docMdata.getFieldName())));
                        }
                    }
                }
                bm.addElement("编码描述").addText("本封装包中“编码数据”元素存储的是计算机文件二进制流的Base64编码，有关Base64编码规则参见IETF RFC 2045多用途邮件扩展（MIME）第一部分：互联网信息体格式。当提取和显现封装在编码数据元素中的计算机文件时，应对Base64编码进行反编码，并依据封装包中“反编码关键字”元素中记录的值还原计算机文件的扩展名");
                bm.addElement("反编码关键字").addText("");
                bm.addElement("编码数据").addText("");
            }
        }
    }

    /**
     * 写入文件
     * @param path
     * @param document
     * @throws IOException
     */
    public void writer(String path,Document document) throws IOException {
        File file = new File(path);
        if(!file.exists()){
            file.mkdirs();
        }
        // 紧凑的格式
        // OutputFormat format = OutputFormat.createCompactFormat();
        // 排版缩进的格式
        OutputFormat format = OutputFormat.createPrettyPrint();
        // 设置编码
        format.setEncoding("UTF-8");
        // 创建XMLWriter对象,指定了写出文件及编码格式
        // XMLWriter writer = new XMLWriter(new FileWriter(new
        // File("src//a.xml")),format);
        XMLWriter writer = new XMLWriter(
                new OutputStreamWriter(new FileOutputStream(new File(path+"档案元数据.xml")), StandardCharsets.UTF_8), format);
        // 写入
        writer.write(document);
        // 立即写入
        writer.flush();
        // 关闭操作
        writer.close();
    }

    /**
     * 获取查询列
     * @param mdataLists
     * @param type
     * @return
     */
    private String getColumn(List<TenantMdataList> mdataLists, Integer type){
        StringBuilder column = new StringBuilder();
        for(TenantMdataList mdata:mdataLists){
            if(mdata.getType() == type){
                column.append(mdata.getFieldName()).append(",");
            }
        }
        if(column.length()>0){
            column.append("IS_DEL");
            if(type == 0 || type==1){
                column.append(",RQ,DH");
            }else if(type == 2){
                column.append(",TYPE,REAL_DOC_NAME,PATH");
            }
        }else {
            throw new ServiceException(type == 3 ? "项目层没有勾选元数据项":(type == 1 ? "卷层":(type == 0 ? "件层":(type == 2 ? "电子文件层":""))) +"没有勾选元数据项");
        }
        return column.toString();
    }

    private String getNull(Object val){
        if(val == null){
            return "";
        }else {
            return String.valueOf(val);
        }
    }

}
